#include "ManagementSystem.h"
#include "StudentInfo.h"
#include <iostream>
#include <fstream>
#include <string>
#define OK 0
typedef int Status;
using namespace std;
ManagementSystem* ManagementSystem::pms = new ManagementSystem();

ManagementSystem* ManagementSystem::GetInstance()
{
    return pms;
}

void ManagementSystem::deleteInstance()
{
    if (pms)
    {
        delete pms;
        pms = nullptr;
    }
}

ManagementSystem::ManagementSystem()
{
    rbStuId = new RBTree(STUID);
    rbScore = new RBTree(SCORE);
    rbCredit = new RBTree(CREDIT);
    rbUsername = new RBTree(USERNAME);
    this->LoadFromFile();
}
ManagementSystem::~ManagementSystem()
{
    delete rbStuId;
    delete rbScore;
    delete rbCredit;
    delete rbUsername;
    this->SaveToFile();
}
Status ManagementSystem::LoadFromFile()
{
    string filename = "./stu_info.txt";
    ifstream ifs;
    ifs.open(filename, ios::in);
    if (ifs.is_open())
    {
        cout << "file open success" << endl;
    }
    else
    {
        cout << "file open failed" << endl;
    }
    StudentInfo* psi;
    string t_name, t_stuId, t_grade, t_pid, t_username, t_password;
    double  t_score, t_credit;
    while (ifs >> t_name)
    {
        psi = new StudentInfo;
        psi->setName(t_name);
        ifs >> t_stuId;psi->setStuId(t_stuId);
        ifs >> t_grade;psi->setGrade(t_grade);
        ifs >> t_pid;psi->setPId(t_pid);
        ifs >> t_score;psi->setScore(t_score);
        ifs >> t_credit;psi->setCredit(t_credit);
        ifs >> t_username;psi->setUsername(t_username);
        ifs >> t_password;psi->setPassword(t_password);
        rbStuId->Insert(psi);
        rbScore->Insert(psi);
        rbCredit->Insert(psi);
        rbUsername->Insert(psi);
    }
    ifs.close();

    return OK;
}

Status ManagementSystem::SaveToFile()
{
    ofstream ofs;
    string filename = "./output.txt";
    ofs.open(filename, ios::out);
    if (ofs.is_open())
    {
        cout << "output open successed" << endl;
    }
    vector<StudentInfo*> vStu = rbStuId->getVec();
    for (auto it = vStu.begin(); it != vStu.end(); ++it)
    {
        ofs << (*it)->getName() << " ";
        ofs << (*it)->getStuId() << " ";
        ofs << (*it)->getGrade() << " ";
        ofs << (*it)->getPId() << " ";
        ofs << (*it)->getScore() << " ";
        ofs << (*it)->getCredit() << " ";
        ofs << (*it)->getUsername() << " ";
        ofs << (*it)->getPassword() << " ";
        ofs << endl;
    }
    ofs.close();

    return OK;
}

// 验证学生身份
bool ManagementSystem::authStudent(Student* s)
{
    StudentInfo cur;
    cur.setUsername(s->getUsername());
    // 根据用户名查找是否有这个学生
    StudentInfo *ret = rbUsername->search(&cur);
    if (ret && ret->getPassword() == s->getPassword())
    {
        s->setInfo(ret);
        return true;
    }
    return false;
}

// 从管理系统中删除，所有树中的相应节点删除，并释放学生信息资源
bool ManagementSystem::remove(StudentInfo* si)
{
    return this->rbStuId->RemoveNode(si) && \
    this->rbScore->RemoveNode(si) && \
    this->rbCredit->RemoveNode(si) && \
    this->rbUsername->RemoveNode(si);
    // 当所有树都需要删除才真正释放学生信息资源
    delete si;
}

// 添加学生信息接口
bool ManagementSystem::addInfo(StudentInfo* newInfo)
{
    return rbStuId->Insert(newInfo) && \
            rbScore->Insert(newInfo) && \
            rbCredit->Insert(newInfo) && \
            rbUsername->Insert(newInfo);
}


